Existing integrated circuits such as programmable logic devices (PLDs) typically utilize “point-to-point” routing, meaning that a path between a source signal generator and one or more destinations is generally fixed at compile time. For example, a typical implementation of an A-to-B connection in a PLD involves connecting logic areas through an interconnect stack of pre-defined horizontal wires. These horizontal wires have a fixed length, are arranged into bundles, and are typically reserved for that A-to-B connection for the entire operation of the PLD's configuration bitstream. Even where a user is able to subsequently change some features of the point-to-point routing, e.g., through partial recompilation, such changes generally apply to block-level replacements, and not to cycle-by-cycle routing implementations.
Such existing routing methods may render the device inefficient, e.g., when the routing is not used every cycle. A first form of inefficiency occurs because of inefficient wire use. In a first example, when an A-to-B connection is rarely used (for example, if the signal value generated by the source logic area at A rarely changes or the destination logic area at B is rarely programmed to be affected by the result), then the conductors used to implement the A-to-B connection may unnecessarily take up metal, power, and/or logic resources. In a second example, when a multiplexed bus having N inputs is implemented in a point-to-point fashion, metal resources may be wasted on routing data from each of the N possible input wires because the multiplexed bus, by definition, outputs only one of the N input wires and ignores the other N−1 input wires. Power resources may also be wasted in these examples when spent in connection with data changes that do not affect a later computation. A more general form of this inefficient wire use occurs when more than one producer generates data that is serialized through a single consumer, or the symmetric case where one producer produces data that is used in a round-robin fashion by a two or more consumers.
A second form of inefficiency, called slack-based inefficiency, occurs when a wire is used, but below its full potential, e.g., in terms of delay. For example, if the data between a producer and a consumer is required to be transmitted every 300 ps, and the conductor between them is capable of transmitting the data in a faster, 100 ps timescale, then the 200 ps of slack time in which the conductor is idle is a form of inefficiency or wasted bandwidth. These two forms of wire underutilization, e.g., inefficient wire use and slack-based inefficiency, can occur separately or together, leading to inefficient use of resources, and wasting valuable wiring, power, and programmable multiplexing resources.
In many cases, the high-level description of the logic implemented on a PLD may already imply sharing of resources, such as sharing access to an external memory or a high-speed transceiver. To do this, it is common to synthesize higher-level structures representing busses onto PLDs. In one example, a software tool may generate an industry-defined bus as Register-Transfer-Level (RTL)/Verilog logic, which is then synthesized into an FPGA device. In this case, however, that shared bus structure is still implemented in the manner discussed above, meaning that it is actually converted into point-to-point static routing. Even in a scheme involving time-multiplexing of FPGA wires, such as the one proposed on pages 22-28 of Trimberger et. al. “A Time Multiplexed FPGA”, Int'l Symposium on FPGAs, 1997, routing is still limited to an individual-wire basis and does not offer grouping capabilities.